// Copyright (c) 2016, the R8 project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
package com.android.tools.r8.utils;

// Helper for collecting timing information during execution.
// Timing t = new Timing("R8");
// A timing tree is collected by calling the following pair (nesting will create the tree):
//     t.begin("My task);
//     try { ... } finally { t.end(); }
// or alternatively:
//     t.scope("My task", () -> { ... });
// Finally a report is printed by:
//     t.report();

import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Stack;

public class Timing {

  private final Stack<Node> stack;

  public Timing(String title) {
    stack = new Stack<>();
    stack.push(new Node("Recorded timings for " + title));
  }

  static class Node {
    final String title;

    final Map<String, Node> children = new LinkedHashMap<>();
    long duration = 0;
    long start_time;

    Node(String title) {
      this.title = title;
      this.start_time = System.nanoTime();
    }

    void restart() {
      assert start_time == -1;
      start_time = System.nanoTime();
    }

    void end() {
      duration += System.nanoTime() - start_time;
      start_time = -1;
      assert duration() >= 0;
    }

    long duration() {
      return duration;
    }

    @Override
    public String toString() {
      return title + ": " + (duration() / 1000000) + "ms.";
    }

    public String toString(Node top) {
      if (this == top) return toString();
      long percentage = duration() * 100 / top.duration();
      return toString() + " (" + percentage + "%)";
    }

    public void report(int depth, Node top) {
      assert duration() >= 0;
      if (depth > 0) {
        for (int i = 0; i < depth; i++) {
          System.out.print("  ");
        }
        System.out.print("- ");
      }
      System.out.println(toString(top));
      children.values().forEach(p -> p.report(depth + 1, top));
    }
  }


  public void begin(String title) {
    Node parent = stack.peek();
    Node child;
    if (parent.children.containsKey(title)) {
      child = parent.children.get(title);
      child.restart();
    } else {
      child = new Node(title);
      parent.children.put(title, child);
    }
    stack.push(child);
  }

  public void end() {
    stack.peek().end();  // record time.
    stack.pop();
  }

  public void report() {
    Node top = stack.peek();
    top.end();
    System.out.println();
    top.report(0, top);
  }

  public void scope(String title, TimingScope fn) {
    begin(title);
    try {
      fn.apply();
    } finally {
      end();
    }
  }

  public interface TimingScope {
    void apply();
  }
}
