22#ifndef LLVM_TRANSFORMS_VECTORIZE_SANDBOXVECTORIZER_DEPENDENCYGRAPH_H 
   23#define LLVM_TRANSFORMS_VECTORIZE_SANDBOXVECTORIZER_DEPENDENCYGRAPH_H 
   63      : OpIt(OpIt), OpItE(OpItE), MemIt(MemIt), 
N(N), DAG(&DAG) {}
 
   66      : OpIt(OpIt), OpItE(OpItE), 
N(N), DAG(&DAG) {}
 
 
  146        PredIterator::skipBadIt(
I->op_begin(), 
I->op_end(), DAG), 
I->op_end(),
 
 
  168      auto IID = 
II->getIntrinsicID();
 
  169      return IID == Intrinsic::stackrestore || IID == Intrinsic::stacksave;
 
 
  177    auto IID = 
I->getIntrinsicID();
 
  178    return IID != Intrinsic::sideeffect && IID != Intrinsic::pseudoprobe;
 
 
  186    return I->mayReadOrWriteMemory() &&
 
 
  193    return I->isFenceLike() &&
 
 
 
  231    assert(
N != 
this && 
"About to point to self!");
 
  233    if (NextMemN != 
nullptr)
 
  234      NextMemN->PrevMemN = 
this;
 
  238    assert(
N != 
this && 
"About to point to self!");
 
  240    if (PrevMemN != 
nullptr)
 
  241      PrevMemN->NextMemN = 
this;
 
  244  void detachFromChain() {
 
  245    if (PrevMemN != 
nullptr)
 
  246      PrevMemN->NextMemN = NextMemN;
 
  247    if (NextMemN != 
nullptr)
 
  248      NextMemN->PrevMemN = PrevMemN;
 
  261    auto OpEndIt = 
I->op_end();
 
  262    return PredIterator(PredIterator::skipBadIt(
I->op_begin(), OpEndIt, DAG),
 
  263                        OpEndIt, MemPreds.begin(), 
this, DAG);
 
 
  266    return PredIterator(
I->op_end(), 
I->op_end(), MemPreds.end(), 
this, DAG);
 
 
  276    [[maybe_unused]] 
auto Inserted = MemPreds.insert(PredN).second;
 
  277    assert(Inserted && 
"PredN already exists!");
 
  278    assert(PredN != 
this && 
"Trying to add a dependency to self!");
 
  279    PredN->MemSuccs.insert(
this);
 
 
  287    MemPreds.erase(PredN);
 
  288    PredN->MemSuccs.erase(
this);
 
 
  296      return MemPreds.count(MN);
 
 
  301    return make_range(MemPreds.begin(), MemPreds.end());
 
 
  305    return make_range(MemSuccs.begin(), MemSuccs.end());
 
 
 
  338  std::optional<Context::CallbackID> CreateInstrCB;
 
  339  std::optional<Context::CallbackID> EraseInstrCB;
 
  340  std::optional<Context::CallbackID> MoveInstrCB;
 
  341  std::optional<Context::CallbackID> SetUseCB;
 
  343  std::unique_ptr<BatchAAResults> BatchAA;
 
  345  enum class DependencyType {
 
  404    CreateInstrCB = Ctx.registerCreateInstrCallback(
 
  406    EraseInstrCB = Ctx.registerEraseInstrCallback(
 
  408    MoveInstrCB = Ctx.registerMoveInstrCallback(
 
  410          notifyMoveInstr(
I, To);
 
  412    SetUseCB = Ctx.registerSetUseCallback(
 
  413        [
this](
const Use &U, 
Value *NewSrc) { notifySetUse(U, NewSrc); });
 
 
  417      Ctx->unregisterCreateInstrCallback(*CreateInstrCB);
 
  419      Ctx->unregisterEraseInstrCallback(*EraseInstrCB);
 
  421      Ctx->unregisterMoveInstrCallback(*MoveInstrCB);
 
  423      Ctx->unregisterSetUseCallback(*SetUseCB);
 
 
  427    auto It = InstrToNodeMap.find(
I);
 
  428    return It != InstrToNodeMap.end() ? It->second.get() : 
nullptr;
 
 
  437    auto [It, NotInMap] = InstrToNodeMap.try_emplace(
I);
 
  440        It->second = std::make_unique<MemDGNode>(
I);
 
  442        It->second = std::make_unique<DGNode>(
I);
 
  444    return It->second.get();
 
 
  452    InstrToNodeMap.clear();
 
 
  458    bool IsEmpty = InstrToNodeMap.empty();
 
  459    assert(IsEmpty == DAGInterval.empty() &&
 
  460           "Interval and InstrToNodeMap out of sync!");
 
 
 
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
 
#define LLVM_TEMPLATE_ABI
 
#define LLVM_DUMP_METHOD
Mark debug helper function definitions like dump() that should not be stripped from debug builds.
 
This file defines the DenseMap class.
 
std::pair< uint64_t, uint64_t > Interval
 
uint64_t IntrinsicInst * II
 
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
 
This class is a wrapper over an AAResults, and it is intended to be used only when there are no IR ch...
 
Represent a node in the directed graph.
 
Implements a dense probed hash-table based set.
 
DenseSetIterator< false > iterator
 
A range adaptor for a pair of iterators.
 
This class implements an extremely fast bulk output stream that can only output to a stream.
 
bool isUsedWithInAlloca() const
Return true if this alloca is used as an inalloca argument to a call.
 
A DependencyGraph Node that points to an Instruction and contains memory dependency edges.
 
void incrUnscheduledSuccs()
 
void decrUnscheduledSuccs()
 
friend class DependencyGraph
 
static bool isMemDepCandidate(Instruction *I)
We consider I as a Memory Dependency Candidate instruction if it reads/write memory or if it has side...
 
virtual iterator preds_end(DependencyGraph &DAG)
 
static bool isMemIntrinsic(IntrinsicInst *I)
\Returns true if intrinsic I touches memory.
 
iterator preds_begin(DependencyGraph &DAG) const
 
DGNode(Instruction *I, DGNodeID ID)
 
unsigned getNumUnscheduledSuccs() const
\Returns the number of unscheduled successors.
 
void setSchedBundle(SchedBundle &SB)
 
bool scheduled() const
\Returns true if this node has been scheduled.
 
unsigned UnscheduledSuccs
The number of unscheduled successors.
 
void setScheduled(bool NewVal)
 
bool ready() const
\Returns true if all dependent successors have been scheduled.
 
iterator_range< iterator > preds(DependencyGraph &DAG) const
\Returns a range of DAG predecessors nodes.
 
iterator preds_end(DependencyGraph &DAG) const
 
SchedBundle * SB
The scheduler bundle that this node belongs to.
 
bool Scheduled
This is true if this node has been scheduled.
 
static bool isMemDepNodeCandidate(Instruction *I)
\Returns true if I is a memory dependency candidate instruction.
 
SchedBundle * getSchedBundle() const
\Returns the scheduling bundle that this node belongs to, or nullptr.
 
DGNodeID SubclassID
For isa/dyn_cast etc.
 
DGNode(const DGNode &Other)=delete
 
static bool isFenceLike(Instruction *I)
\Returns true if I is fence like. It excludes non-mem intrinsics.
 
void resetScheduleState()
 
Instruction * getInstruction() const
 
static bool isStackSaveOrRestoreIntrinsic(Instruction *I)
 
bool comesBefore(const DGNode *Other)
\Returns true if this is before Other in program order.
 
friend raw_ostream & operator<<(raw_ostream &OS, DGNode &N)
 
virtual iterator preds_begin(DependencyGraph &DAG)
 
Interval< Instruction > getInterval() const
\Returns the range of instructions included in the DAG.
 
bool empty() const
\Returns true if the DAG's state is clear. Used in assertions.
 
LLVM_DUMP_METHOD void dump() const
 
DGNode * getNode(Instruction *I) const
 
DependencyGraph(AAResults &AA, Context &Ctx)
This constructor also registers callbacks.
 
DGNode * getNodeOrNull(Instruction *I) const
Like getNode() but returns nullptr if I is nullptr.
 
void print(raw_ostream &OS) const
 
DGNode * getOrCreateNode(Instruction *I)
 
LLVM_ABI Interval< Instruction > extend(ArrayRef< Instruction * > Instrs)
Build/extend the dependency graph such that it includes Instrs.
 
A sandboxir::User with operands, opcode and linked with previous/next instructions in an instruction ...
 
Convenience builders for a MemDGNode interval.
 
static LLVM_ABI MemDGNode * getBotMemDGNode(const Interval< Instruction > &Intvl, const DependencyGraph &DAG)
Scans the instruction chain in Intvl bottom-up, returning the bottom-most MemDGNode,...
 
static Interval< MemDGNode > makeEmpty()
 
static LLVM_ABI MemDGNode * getTopMemDGNode(const Interval< Instruction > &Intvl, const DependencyGraph &DAG)
Scans the instruction chain in Intvl top-down, returning the top-most MemDGNode, or nullptr.
 
static LLVM_ABI Interval< MemDGNode > make(const Interval< Instruction > &Instrs, DependencyGraph &DAG)
Given Instrs it finds their closest mem nodes in the interval and returns the corresponding mem range...
 
A DependencyGraph Node for instructions that may read/write memory, or have some ordering constraints...
 
iterator preds_end(DependencyGraph &DAG) override
 
friend class DependencyGraph
 
iterator preds_begin(DependencyGraph &DAG) override
 
bool hasMemPred(DGNode *N) const
\Returns true if there is a memory dependency N->this.
 
static bool classof(const DGNode *Other)
 
iterator_range< DenseSet< MemDGNode * >::const_iterator > memPreds() const
\Returns all memory dependency predecessors. Used by tests.
 
MemDGNode * getNextNode() const
\Returns the next Mem DGNode in instruction order.
 
iterator_range< DenseSet< MemDGNode * >::const_iterator > memSuccs() const
\Returns all memory dependency successors.
 
void removeMemPred(MemDGNode *PredN)
Removes the memory dependency PredN->this.
 
MemDGNode(Instruction *I)
 
MemDGNode * getPrevNode() const
\Returns the previous Mem DGNode in instruction order.
 
void addMemPred(MemDGNode *PredN)
Adds the mem dependency edge PredN->this.
 
friend class PredIterator
 
Iterate over both def-use and mem dependencies.
 
std::ptrdiff_t difference_type
 
PredIterator operator++(int)
 
bool operator!=(const PredIterator &Other) const
 
LLVM_ABI PredIterator & operator++()
 
std::input_iterator_tag iterator_category
 
The nodes that need to be scheduled back-to-back in a single scheduling cycle form a SchedBundle.
 
Represents a Def-use/Use-def edge in SandboxIR.
 
OperandUseIterator op_iterator
 
A SandboxIR Value has users. This is the base class.
 
This provides a very simple, boring adaptor for a begin and end iterator into a range type.
 
Abstract Attribute helper functions.
 
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
 
DGNodeID
SubclassIDs for isa/dyn_cast etc.
 
void dump(const SparseBitVector< ElementSize > &LHS, raw_ostream &out)
 
Printable print(const GCNRegPressure &RP, const GCNSubtarget *ST=nullptr, unsigned DynamicVGPRBlockSize=0)
 
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
 
APInt operator*(APInt a, uint64_t RHS)
 
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
 
bool operator==(const AddressRangeValuePair &LHS, const AddressRangeValuePair &RHS)
 
Implement std::hash so that hash_code can be used in STL containers.