// Copyright 2011 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#ifndef NINJA_METRICS_H_
#define NINJA_METRICS_H_

#include <atomic>
#include <mutex>
#include <string>
#include <vector>
using namespace std;

#include "util.h"  // For int64_t.

struct Status;

/// The Metrics module is used for the debug mode that dumps timing stats of
/// various actions.  To use, see METRIC_RECORD below.

/// A single metrics we're tracking, like "depfile load time".
struct Metric {
  Metric(const std::string& name) : name_(name) {}

  void AddResult(int count, int64_t time_us) {
    thread_local size_t this_slot = GetThreadSlotIndex();
    Slot& slot = slots_[this_slot];
    slot.count += count;
    slot.time += time_us;
  }

  const std::string& name() const { return name_; }

  int count() const {
    int result = 0;
    for (const Slot& slot : slots_) {
      result += slot.count;
    }
    return result;
  }

  int64_t time() const {
    int64_t result = 0;
    for (const Slot& slot : slots_) {
      result += slot.time;
    }
    return result;
  }

private:
  /// Try to give each thread a different slot to reduce thread contention.
  struct NINJA_ALIGNAS_CACHE_LINE Slot {
    /// Number of times we've hit the code path.
    std::atomic<int> count {};
    /// Total time (in micros) we've spent on the code path.
    std::atomic<int64_t> time {};
  };

  std::string name_;
  std::vector<Slot> slots_ { GetThreadSlotCount() };
};

/// A scoped object for recording a metric across the body of a function.
/// Used by the METRIC_RECORD macro. Inline the metric_ null check to minimize
/// the effect on the typical case where metrics are disabled.
struct ScopedMetric {
  explicit ScopedMetric(Metric* metric) : metric_(metric) {
    if (metric_ == nullptr) {
      return;
    }
    RecordStart();
  }

  ~ScopedMetric() {
    if (metric_ == nullptr) {
      return;
    }
    RecordResult();
  }

private:
  void RecordStart();
  void RecordResult();

  Metric* metric_;
  /// Timestamp when the measurement started.
  /// Value is platform-dependent.
  int64_t start_;
};

/// The singleton that stores metrics and prints the report.
struct Metrics {
  Metric* NewMetric(const string& name);

  /// Print a summary report to stdout.
  void Report(Status *status);

private:
  std::mutex mutex_;
  vector<Metric*> metrics_;
};

/// Get the current time as relative to some epoch.
/// Epoch varies between platforms; only useful for measuring elapsed time.
int64_t GetTimeMillis();

/// A simple stopwatch which returns the time
/// in seconds since Restart() was called.
struct Stopwatch {
 public:
  Stopwatch() : started_(0) {}

  /// Seconds since Restart() call.
  double Elapsed() const {
    return 1e-6 * static_cast<double>(Now() - started_);
  }

  void Restart() { started_ = Now(); }

 private:
  uint64_t started_;
  uint64_t Now() const;
};

/// The primary interface to metrics.  Use METRIC_RECORD("foobar") at the top
/// of a function to get timing stats recorded for each call of the function.
#define METRIC_RECORD(name)                                             \
  static Metric* metrics_h_metric =                                     \
      g_metrics ? g_metrics->NewMetric(name) : NULL;                    \
  ScopedMetric metrics_h_scoped(metrics_h_metric);

extern Metrics* g_metrics;

void DumpMemoryUsage(Status *status);

#endif // NINJA_METRICS_H_
