1 //  Copyright (c) 2013, Facebook, Inc.  All rights reserved.
2 //  This source code is licensed under both the GPLv2 (found in the
3 //  COPYING file in the root directory) and Apache 2.0 License
4 //  (found in the LICENSE.Apache file in the root directory).
5 //
6 // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
7 // Use of this source code is governed by a BSD-style license that can be
8 // found in the LICENSE file. See the AUTHORS file for names of contributors.
9 
10 #pragma once
11 
12 #include "monitoring/histogram.h"
13 #include "rocksdb/env.h"
14 
15 namespace ROCKSDB_NAMESPACE {
16 
17 class HistogramWindowingImpl : public Histogram
18 {
19 public:
20   HistogramWindowingImpl();
21   HistogramWindowingImpl(uint64_t num_windows,
22                          uint64_t micros_per_window,
23                          uint64_t min_num_per_window);
24 
25   HistogramWindowingImpl(const HistogramWindowingImpl&) = delete;
26   HistogramWindowingImpl& operator=(const HistogramWindowingImpl&) = delete;
27 
28   ~HistogramWindowingImpl();
29 
30   virtual void Clear() override;
31   virtual bool Empty() const override;
32   virtual void Add(uint64_t value) override;
33   virtual void Merge(const Histogram& other) override;
34   void Merge(const HistogramWindowingImpl& other);
35 
36   virtual std::string ToString() const override;
Name()37   virtual const char* Name() const override { return "HistogramWindowingImpl"; }
min()38   virtual uint64_t min() const override { return stats_.min(); }
max()39   virtual uint64_t max() const override { return stats_.max(); }
num()40   virtual uint64_t num() const override { return stats_.num(); }
41   virtual double Median() const override;
42   virtual double Percentile(double p) const override;
43   virtual double Average() const override;
44   virtual double StandardDeviation() const override;
45   virtual void Data(HistogramData* const data) const override;
46 
47 private:
48   void TimerTick();
49   void SwapHistoryBucket();
current_window()50   inline uint64_t current_window() const {
51     return current_window_.load(std::memory_order_relaxed);
52   }
last_swap_time()53   inline uint64_t last_swap_time() const{
54     return last_swap_time_.load(std::memory_order_relaxed);
55   }
56 
57   Env* env_;
58   std::mutex mutex_;
59 
60   // Aggregated stats over windows_stats_, all the computation is done
61   // upon aggregated values
62   HistogramStat stats_;
63 
64   // This is a circular array representing the latest N time-windows.
65   // Each entry stores a time-window of data. Expiration is done
66   // on window-based.
67   std::unique_ptr<HistogramStat[]> window_stats_;
68 
69   std::atomic_uint_fast64_t current_window_;
70   std::atomic_uint_fast64_t last_swap_time_;
71 
72   // Following parameters are configuable
73   uint64_t num_windows_ = 5;
74   uint64_t micros_per_window_ = 60000000;
75   // By default, don't care about the number of values in current window
76   // when decide whether to swap windows or not.
77   uint64_t min_num_per_window_ = 0;
78 };
79 
80 }  // namespace ROCKSDB_NAMESPACE
81