//===- RemarkCounter.h ----------------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
//
// Generic tool to count remarks based on properties
//
//===----------------------------------------------------------------------===//
#ifndef TOOLS_LLVM_REMARKCOUNTER_H
#define TOOLS_LLVM_REMARKCOUNTER_H
#include "RemarkUtilHelpers.h"
#include "llvm/ADT/MapVector.h"
#include "llvm/Support/Regex.h"

namespace llvm {
namespace remarks {

/// Collect remarks by counting the existance of a remark or by looking through
/// the keys and summing through the total count.
enum class CountBy { REMARK, ARGUMENT };

/// Summarize the count by either emitting one count for the remark file, or
/// grouping the count by source file or by function name.
enum class GroupBy {
  TOTAL,
  PER_SOURCE,
  PER_FUNCTION,
  PER_FUNCTION_WITH_DEBUG_LOC
};

/// Convert \p GroupBy to a std::string.
inline std::string groupByToStr(GroupBy GroupBy) {
  switch (GroupBy) {
  default:
    return "Total";
  case GroupBy::PER_FUNCTION:
    return "Function";
  case GroupBy::PER_FUNCTION_WITH_DEBUG_LOC:
    return "FuctionWithDebugLoc";
  case GroupBy::PER_SOURCE:
    return "Source";
  }
}

/// Filter out remarks based on remark properties based on name, pass name,
/// argument and type.
struct Filters {
  std::optional<FilterMatcher> RemarkNameFilter;
  std::optional<FilterMatcher> PassNameFilter;
  std::optional<FilterMatcher> ArgFilter;
  std::optional<Type> RemarkTypeFilter;

  /// Returns true if \p Remark satisfies all the provided filters.
  bool filterRemark(const Remark &Remark);
};

/// Abstract counter class used to define the general required methods for
/// counting a remark.
struct Counter {
  GroupBy Group = GroupBy::TOTAL;
  Counter() = default;
  Counter(enum GroupBy GroupBy) : Group(GroupBy) {}
  /// Obtain the field for collecting remark info based on how we are
  /// collecting. Remarks are grouped by FunctionName, Source, Source and
  /// Function or collect by file.
  std::optional<std::string> getGroupByKey(const Remark &Remark);

  /// Collect count information from \p Remark organized based on \p Group
  /// property.
  virtual void collect(const Remark &) = 0;
  /// Output the final count to the file \p OutputFileName
  virtual Error print(StringRef OutputFileName) = 0;
  virtual ~Counter() = default;
};

/// Count remarks based on the provided \p Keys argument and summing up the
/// value for each matching key organized by source, function or reporting a
/// total for the specified remark file.
/// Reporting count grouped by source:
///
///  | source        | key1 | key2 | key3 |
///  |---------------|------|------|------|
///  | path/to/file1 | 0    | 1    | 3    |
///  | path/to/file2 | 1    | 0    | 2    |
///  | path/to/file3 | 2    | 3    | 1    |
///
/// Reporting count grouped by function:
///
///  | Function      | key1 | key2 | key3 |
///  |---------------|------|------|------|
///  | function1     | 0    | 1    | 3    |
///  | function2     | 1    | 0    | 2    |
///  | function3     | 2    | 3    | 1    |
struct ArgumentCounter : Counter {
  /// The internal object to keep the count for the remarks. The first argument
  /// corresponds to the property we are collecting for this can be either a
  /// source or function. The second argument is a row of integers where each
  /// item in the row is the count for a specified key.
  std::map<std::string, SmallVector<unsigned, 4>> CountByKeysMap;
  /// A set of all the remark argument found in the remark file. The second
  /// argument is the index of each of those arguments which can be used in
  /// `CountByKeysMap` to fill count information for that argument.
  MapVector<StringRef, unsigned> ArgumentSetIdxMap;
  /// Create an argument counter. If the provided \p Arguments represent a regex
  /// vector then we need to check that the provided regular expressions are
  /// valid if not we return an Error.
  static Expected<ArgumentCounter>
  createArgumentCounter(GroupBy Group, ArrayRef<FilterMatcher> Arguments,
                        StringRef Buffer, Filters &Filter) {
    ArgumentCounter AC;
    AC.Group = Group;
    if (auto E = AC.getAllMatchingArgumentsInRemark(Buffer, Arguments, Filter))
      return std::move(E);
    return AC;
  }

  /// Update the internal count map based on the remark integer arguments that
  /// correspond the the user specified argument keys to collect for.
  void collect(const Remark &) override;

  /// Print a CSV table consisting of an index which is specified by \p
  /// `Group` and can be a function name, source file name or function name
  /// with the full source path and columns of user specified remark arguments
  /// to collect the count for.
  Error print(StringRef OutputFileName) override;

private:
  /// collect all the arguments that match the list of \p Arguments provided by
  /// parsing through \p Buffer of remarks and filling \p ArgumentSetIdxMap
  /// acting as a row for for all the keys that we are interested in collecting
  /// information for.
  Error getAllMatchingArgumentsInRemark(StringRef Buffer,
                                        ArrayRef<FilterMatcher> Arguments,
                                        Filters &Filter);
};

/// Collect remarks based by counting the existance of individual remarks. The
/// reported table will be structured based on the provided \p Group argument
/// by reporting count for functions, source or total count for the provided
/// remark file.
struct RemarkCounter : Counter {
  std::map<std::string, unsigned> CountedByRemarksMap;
  RemarkCounter(GroupBy Group) : Counter(Group) {}

  /// Advance the internal map count broken by \p Group when
  /// seeing \p Remark.
  void collect(const Remark &) override;

  /// Print a CSV table consisting of an index which is specified by \p
  /// `Group` and can be a function name, source file name or function name
  /// with the full source path and a counts column corresponding to the count
  /// of each individual remark at th index.
  Error print(StringRef OutputFileName) override;
};
} // namespace remarks

} // namespace llvm
#endif // TOOLS_LLVM_REMARKCOUNTER_H
