//===- subzero/src/IceRegAlloc.h - Linear-scan reg. allocation --*- C++ -*-===//
//
//                        The Subzero Code Generator
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
///
/// \file
/// \brief Declares the LinearScan data structure used during linear-scan
/// register allocation.
///
/// This holds the various work queues for the linear-scan algorithm.
///
//===----------------------------------------------------------------------===//

#ifndef SUBZERO_SRC_ICEREGALLOC_H
#define SUBZERO_SRC_ICEREGALLOC_H

#include "IceDefs.h"
#include "IceBitVector.h"
#include "IceOperand.h"
#include "IceTypes.h"

namespace Ice {

class LinearScan {
  LinearScan() = delete;
  LinearScan(const LinearScan &) = delete;
  LinearScan &operator=(const LinearScan &) = delete;

public:
  explicit LinearScan(Cfg *Func);
  void init(RegAllocKind Kind, CfgSet<Variable *> ExcludeVars = {});
  void scan(const SmallBitVector &RegMask, bool Randomized);
  // Returns the number of times some variable has been assigned a register but
  // later evicted because of a higher-priority allocation.  The idea is that we
  // can implement "second-chance bin-packing" by rerunning register allocation
  // until there are no more evictions.
  SizeT getNumEvictions() const { return Evicted.size(); }
  bool hasEvictions() const { return !Evicted.empty(); }
  void dump(Cfg *Func) const;

  // TODO(stichnot): Statically choose the size based on the target being
  // compiled.  For now, choose a value large enough to fit into the
  // SmallVector's fixed portion, which is 32 for x86-32, 84 for x86-64, and 102
  // for ARM32.
  static constexpr size_t REGS_SIZE = 128;

private:
  using OrderedRanges = CfgVector<Variable *>;
  using UnorderedRanges = CfgVector<Variable *>;
  using DefUseErrorList = llvm::SmallVector<SizeT, 10>;

  class IterationState {
    IterationState(const IterationState &) = delete;
    IterationState operator=(const IterationState &) = delete;

  public:
    IterationState() = default;
    Variable *Cur = nullptr;
    Variable *Prefer = nullptr;
    RegNumT PreferReg;
    bool AllowOverlap = false;
    SmallBitVector RegMask;
    SmallBitVector RegMaskUnfiltered;
    SmallBitVector Free;
    SmallBitVector FreeUnfiltered;
    SmallBitVector PrecoloredUnhandledMask; // Note: only used for dumping
    llvm::SmallVector<RegWeight, REGS_SIZE> Weights;
  };

  bool livenessValidateIntervals(const DefUseErrorList &DefsWithoutUses,
                                 const DefUseErrorList &UsesBeforeDefs,
                                 const CfgVector<InstNumberT> &LRBegin,
                                 const CfgVector<InstNumberT> &LREnd) const;
  void initForGlobal();
  void initForInfOnly();
  void initForSecondChance();
  /// Move an item from the From set to the To set. From[Index] is pushed onto
  /// the end of To[], then the item is efficiently removed from From[] by
  /// effectively swapping it with the last item in From[] and then popping it
  /// from the back. As such, the caller is best off iterating over From[] in
  /// reverse order to avoid the need for special handling of the iterator.
  void moveItem(UnorderedRanges &From, SizeT Index, UnorderedRanges &To) {
    To.push_back(From[Index]);
    From[Index] = From.back();
    From.pop_back();
  }

  /// \name scan helper functions.
  /// @{
  /// Free up a register for infinite-weight Cur by spilling and reloading some
  /// register that isn't used during Cur's live range.
  void addSpillFill(IterationState &Iter);
  /// Check for active ranges that have expired or become inactive.
  void handleActiveRangeExpiredOrInactive(const Variable *Cur);
  /// Check for inactive ranges that have expired or reactivated.
  void handleInactiveRangeExpiredOrReactivated(const Variable *Cur);
  void findRegisterPreference(IterationState &Iter);
  void filterFreeWithInactiveRanges(IterationState &Iter);
  void filterFreeWithPrecoloredRanges(IterationState &Iter);
  void allocatePrecoloredRegister(Variable *Cur);
  void allocatePreferredRegister(IterationState &Iter);
  void allocateFreeRegister(IterationState &Iter, bool Filtered);
  void handleNoFreeRegisters(IterationState &Iter);
  void assignFinalRegisters(const SmallBitVector &RegMaskFull,
                            const SmallBitVector &PreDefinedRegisters,
                            bool Randomized);
  /// @}

  void dumpLiveRangeTrace(const char *Label, const Variable *Item);

  Cfg *const Func;
  GlobalContext *const Ctx;
  TargetLowering *const Target;

  OrderedRanges Unhandled;
  /// UnhandledPrecolored is a subset of Unhandled, specially collected for
  /// faster processing.
  OrderedRanges UnhandledPrecolored;
  UnorderedRanges Active, Inactive, Handled;
  UnorderedRanges Evicted;
  CfgVector<InstNumberT> Kills;
  RegAllocKind Kind = RAK_Unknown;
  /// RegUses[I] is the number of live ranges (variables) that register I is
  /// currently assigned to. It can be greater than 1 as a result of
  /// AllowOverlap inference.
  llvm::SmallVector<int32_t, REGS_SIZE> RegUses;
  llvm::SmallVector<const SmallBitVector *, REGS_SIZE> RegAliases;
  bool FindPreference = false;
  bool FindOverlap = false;
  const bool Verbose;
  const bool UseReserve;
  CfgVector<Variable *> Vars;
};

} // end of namespace Ice

#endif // SUBZERO_SRC_ICEREGALLOC_H
