// Copyright (c) 2019 Google LLC
//
// 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 SOURCE_FUZZ_EQUIVALENCE_RELATION_H_
#define SOURCE_FUZZ_EQUIVALENCE_RELATION_H_

#include <memory>
#include <unordered_map>
#include <unordered_set>
#include <vector>

#include "source/util/make_unique.h"

namespace spvtools {
namespace fuzz {

// A class for representing an equivalence relation on objects of type |T|,
// which should be a value type.  The type |T| is required to have a copy
// constructor, and |PointerHashT| and |PointerEqualsT| must be functors
// providing hashing and equality testing functionality for pointers to objects
// of type |T|.
//
// A disjoint-set (a.k.a. union-find or merge-find) data structure is used to
// represent the equivalence relation.  Path compression is used.  Union by
// rank/size is not used.
//
// Each disjoint set is represented as a tree, rooted at the representative
// of the set.
//
// Getting the representative of a value simply requires chasing parent pointers
// from the value until you reach the root.
//
// Checking equivalence of two elements requires checking that the
// representatives are equal.
//
// Traversing the tree rooted at a value's representative visits the value's
// equivalence class.
//
// |PointerHashT| and |PointerEqualsT| are used to define *equality* between
// values, and otherwise are *not* used to define the equivalence relation
// (except that equal values are equivalent).  The equivalence relation is
// constructed by repeatedly adding pairs of (typically non-equal) values that
// are deemed to be equivalent.
//
// For example in an equivalence relation on integers, 1 and 5 might be added
// as equivalent, so that IsEquivalent(1, 5) holds, because they represent
// IDs in a SPIR-V binary that are known to contain the same value at run time,
// but clearly 1 != 5.  Since 1 and 1 are equal, IsEquivalent(1, 1) will also
// hold.
//
// Each unique (up to equality) value added to the relation is copied into
// |owned_values_|, so there is one canonical memory address per unique value.
// Uniqueness is ensured by storing (and checking) a set of pointers to these
// values in |value_set_|, which uses |PointerHashT| and |PointerEqualsT|.
//
// |parent_| and |children_| encode the equivalence relation, i.e., the trees.
template <typename T, typename PointerHashT, typename PointerEqualsT>
class EquivalenceRelation {
 public:
  // Requires that |value1| and |value2| are already registered in the
  // equivalence relation.  Merges the equivalence classes associated with
  // |value1| and |value2|.
  void MakeEquivalent(const T& value1, const T& value2) {
    assert(Exists(value1) &&
           "Precondition: value1 must already be registered.");
    assert(Exists(value2) &&
           "Precondition: value2 must already be registered.");

    // Look up canonical pointers to each of the values in the value pool.
    const T* value1_ptr = *value_set_.find(&value1);
    const T* value2_ptr = *value_set_.find(&value2);

    // If the values turn out to be identical, they are already in the same
    // equivalence class so there is nothing to do.
    if (value1_ptr == value2_ptr) {
      return;
    }

    // Find the representative for each value's equivalence class, and if they
    // are not already in the same class, make one the parent of the other.
    const T* representative1 = Find(value1_ptr);
    const T* representative2 = Find(value2_ptr);
    assert(representative1 && "Representatives should never be null.");
    assert(representative2 && "Representatives should never be null.");
    if (representative1 != representative2) {
      parent_[representative1] = representative2;
      children_[representative2].push_back(representative1);
    }
  }

  // Requires that |value| is not known to the equivalence relation. Registers
  // it in its own equivalence class and returns a pointer to the equivalence
  // class representative.
  const T* Register(const T& value) {
    assert(!Exists(value));

    // This relies on T having a copy constructor.
    auto unique_pointer_to_value = MakeUnique<T>(value);
    auto pointer_to_value = unique_pointer_to_value.get();
    owned_values_.push_back(std::move(unique_pointer_to_value));
    value_set_.insert(pointer_to_value);

    // Initially say that the value is its own parent and that it has no
    // children.
    assert(pointer_to_value && "Representatives should never be null.");
    parent_[pointer_to_value] = pointer_to_value;
    children_[pointer_to_value] = std::vector<const T*>();

    return pointer_to_value;
  }

  // Returns exactly one representative per equivalence class.
  std::vector<const T*> GetEquivalenceClassRepresentatives() const {
    std::vector<const T*> result;
    for (auto& value : owned_values_) {
      if (parent_[value.get()] == value.get()) {
        result.push_back(value.get());
      }
    }
    return result;
  }

  // Returns pointers to all values in the equivalence class of |value|, which
  // must already be part of the equivalence relation.
  std::vector<const T*> GetEquivalenceClass(const T& value) const {
    assert(Exists(value));

    std::vector<const T*> result;

    // Traverse the tree of values rooted at the representative of the
    // equivalence class to which |value| belongs, and collect up all the values
    // that are encountered.  This constitutes the whole equivalence class.
    std::vector<const T*> stack;
    stack.push_back(Find(*value_set_.find(&value)));
    while (!stack.empty()) {
      const T* item = stack.back();
      result.push_back(item);
      stack.pop_back();
      for (auto child : children_[item]) {
        stack.push_back(child);
      }
    }
    return result;
  }

  // Returns true if and only if |value1| and |value2| are in the same
  // equivalence class.  Both values must already be known to the equivalence
  // relation.
  bool IsEquivalent(const T& value1, const T& value2) const {
    return Find(&value1) == Find(&value2);
  }

  // Returns all values known to be part of the equivalence relation.
  std::vector<const T*> GetAllKnownValues() const {
    std::vector<const T*> result;
    for (auto& value : owned_values_) {
      result.push_back(value.get());
    }
    return result;
  }

  // Returns true if and only if |value| is known to be part of the equivalence
  // relation.
  bool Exists(const T& value) const {
    return value_set_.find(&value) != value_set_.end();
  }

  // Returns the representative of the equivalence class of |value|, which must
  // already be known to the equivalence relation.  This is the 'Find' operation
  // in a classic union-find data structure.
  const T* Find(const T* value) const {
    assert(Exists(*value));

    // Get the canonical pointer to the value from the value pool.
    const T* known_value = *value_set_.find(value);
    assert(parent_[known_value] && "Every known value should have a parent.");

    // Compute the result by chasing parents until we find a value that is its
    // own parent.
    const T* result = known_value;
    while (parent_[result] != result) {
      result = parent_[result];
    }
    assert(result && "Representatives should never be null.");

    // At this point, |result| is the representative of the equivalence class.
    // Now perform the 'path compression' optimization by doing another pass up
    // the parent chain, setting the parent of each node to be the
    // representative, and rewriting children correspondingly.
    const T* current = known_value;
    while (parent_[current] != result) {
      const T* next = parent_[current];
      parent_[current] = result;
      children_[result].push_back(current);
      auto child_iterator =
          std::find(children_[next].begin(), children_[next].end(), current);
      assert(child_iterator != children_[next].end() &&
             "'next' is the parent of 'current', so 'current' should be a "
             "child of 'next'");
      children_[next].erase(child_iterator);
      current = next;
    }
    return result;
  }

 private:
  // Maps every value to a parent.  The representative of an equivalence class
  // is its own parent.  A value's representative can be found by walking its
  // chain of ancestors.
  //
  // Mutable because the intuitively const method, 'Find', performs path
  // compression.
  mutable std::unordered_map<const T*, const T*> parent_;

  // Stores the children of each value.  This allows the equivalence class of
  // a value to be calculated by traversing all descendents of the class's
  // representative.
  //
  // Mutable because the intuitively const method, 'Find', performs path
  // compression.
  mutable std::unordered_map<const T*, std::vector<const T*>> children_;

  // The values known to the equivalence relation are allocated in
  // |owned_values_|, and |value_pool_| provides (via |PointerHashT| and
  // |PointerEqualsT|) a means for mapping a value of interest to a pointer
  // into an equivalent value in |owned_values_|.
  std::unordered_set<const T*, PointerHashT, PointerEqualsT> value_set_;
  std::vector<std::unique_ptr<T>> owned_values_;
};

}  // namespace fuzz
}  // namespace spvtools

#endif  // SOURCE_FUZZ_EQUIVALENCE_RELATION_H_
