// Copyright 2019 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef TOOLS_FIDLCAT_LIB_COMPARATOR_H_
#define TOOLS_FIDLCAT_LIB_COMPARATOR_H_

#include <deque>
#include <fstream>
#include <map>
#include <memory>
#include <sstream>
#include <string>
#include <string_view>
#include <utility>

#include "tools/fidlcat/lib/message_graph.h"

namespace fidlcat {

// To compare the messages stored in the golden file to the messages intercepted by fidlcat in the
// current execution, this class first builds a GoldenMessageGraph from the golden file when
// initialized. It also creates an empty ActualMessageGraph, actual_message_graph_, for the current
// execution. Then for each message passed to CompareInput or CompareOutput, it updates
// actual_message_graph_ by inserting the new message in it. If this message can be matched uniquely
// to a message from the golden_message_graph_, we record it, and try to propagate this matching
// along dependenies in the graphs. When there are no more messages to receive, that is to say when
// FinishComparison is called, we propagate (along dependencies) and reverse propagate
// (along reverse dependencies) matchings for all nodes.
class Comparator {
 public:
  Comparator(std::string_view compare_file_name, std::ostream& os) : compare_results_(os) {
    std::string golden_file_contents;
    std::ifstream compare_file(compare_file_name);
    golden_file_contents.assign((std::istreambuf_iterator<char>(compare_file)),
                                (std::istreambuf_iterator<char>()));
    ParseGolden(golden_file_contents);
  }

  // Creates a new node in actual_message_graph_ and tries to match.
  void CompareInput(std::string_view syscall_inputs, std::string_view actual_process_name,
                    uint64_t actual_pid, uint64_t actual_tid);

  void CompareOutput(std::string_view syscall_outputs, std::string_view actual_process_name,
                     uint64_t actual_pid, uint64_t actual_tid);

  // As the golden file should not contain any error, any error in the actual execution results in
  // an error message.
  void DecodingError(std::string_view error);

  // Tries, using all the information in golden_message_graph_ and actual_message_graph_, to match
  // as many nodes as possible to one another, and outputs the result of the comparison.
  void FinishComparison();

 protected:
  // For testing, expected_output_ should then be set using ParseGolden.
  Comparator(std::ostream& os) : compare_results_(os) {}

  // Given a message node for the current execution, see if it can be uniquely matched with a golden
  // message node. If there is exactly one golden node that could match returns it, and returns
  // nullptr otherwise. In case no golden node could match this message, outputs an error to
  // compare_results_.
  std::shared_ptr<GoldenMessageNode> UniqueMatchToGolden(
      std::shared_ptr<ActualMessageNode> actual_message_node);

  // Given an actual node and the golden node that should match it, checks that this match is
  // possible (neither node is already matched, and they have the same number of dependencies), and
  // recursively propagates this matching along all dependency links. Returns false if an
  // inconsistency in the matching is found. If reverse_propagate is set to true, also runs
  // ReversePropagate on actual_node.
  bool PropagateMatch(std::shared_ptr<ActualNode> actual_node,
                      std::shared_ptr<GoldenNode> golden_node, bool reverse_propagate);

  // Given an actual node with a matching golden node, propagates this matching
  // along the reverse dependency links of actual_node and alls PropagateMatch(with
  // reverse_propagate set to true) for any new node matched. Returns false if an inconsistency in
  // the matching was found while propagating.
  // Assumes that PropagateMatch was called successfully on actual_node before, in particular that
  // actual_node->matching_golden_node() is not null, and that the actual_message_graph_ is
  // complete, that is to say no more messages/nodes/links will be added to it.
  // Note: this function relies on PropagateMatching to take care of recursion termination, and
  // never calls itself directly (the code here could be inserted at the end of PropagateMatch with
  // the same behavior).
  bool ReversePropagateMatch(std::shared_ptr<ActualNode> actual_node);

  // Creates the golden_message_graph_ from the contents of the file.
  void ParseGolden(std::string_view golden_file_contents);

  // Returns the first block of syscall input or output from messages, and stores the number of
  // characters processed in processed_char_count (which may be different from the length of the
  // message if some lines from messages were ignored).
  static std::string_view GetMessage(std::string_view messages, size_t* processed_char_count);

  // golden_message_graph contains all the information about the execution saved in the golden file,
  // while acutal_message_graph is constructed progressively, every time fidlcat intercepts a
  // message in the current execution.
  GoldenMessageGraph golden_message_graph_;
  ActualMessageGraph actual_message_graph_;

  // We need this map to link output messages to their corresponding input messages.
  std::map<uint64_t, std::shared_ptr<ActualMessageNode>> last_unmatched_input_from_tid_;

 private:
  std::ostream& compare_results_;

  // Returns true if line is the final line of a multiline request/response (ie begins with the
  // proper number of spaces as indentation, then a sequence of " }" or " ]") We rely here on
  // fidl_codec printing: it indents all the contents of a message by at least (indentation of
  // beginning of message + 1), and the last line of the message will be a line containing exactly
  // the same indentation as the beginning of the message and one or more closing brackets.
  static bool ClosingSequence(std::string_view line, size_t indentation);

  // Returns true if line is not part of a message (ie a fidlcat startup indication or a newline).
  static bool IgnoredLine(std::string_view line);

  // Expects decimal numbers.
  static uint64_t ExtractUint64(std::string_view str);

  // Removes the header (process name pid:tid) from a message. If there is no header, returns the
  // string unchanged. If pid, tid and process_name pointers are passed as arguments, updates them
  // if a header was present, leaves them unchanged otherwise.
  static std::string_view AnalyzesAndRemovesHeader(std::string_view message,
                                                   std::string* process_name = nullptr,
                                                   uint64_t* pid = nullptr,
                                                   uint64_t* tid = nullptr);

  // Returns true if message is the input message of a syscall with no return value.
  static bool HasReturn(std::string_view message);
};

}  // namespace fidlcat

#endif  // TOOLS_FIDLCAT_LIB_COMPARATOR_H_
