47 auto getOperandIndexIfPred =
50 branch.getSuccessorRegions(pred, successors);
52 if (successor.getSuccessor() != region)
55 ValueRange inputs = successor.getSuccessorInputs();
57 output.push_back(inputValue);
60 unsigned firstInputIndex, lastInputIndex;
62 firstInputIndex = cast<BlockArgument>(inputs[0]).getArgNumber();
63 lastInputIndex = cast<BlockArgument>(inputs.back()).getArgNumber();
65 firstInputIndex = cast<OpResult>(inputs[0]).getResultNumber();
66 lastInputIndex = cast<OpResult>(inputs.back()).getResultNumber();
68 if (firstInputIndex > inputIndex || lastInputIndex < inputIndex) {
69 output.push_back(inputValue);
72 return inputIndex - firstInputIndex;
82 if (std::optional<unsigned> operandIndex =
85 branch.getEntrySuccessorOperands(branchPoint)[*operandIndex], maxDepth,
91 if (std::optional<unsigned> operandIndex = getOperandIndexIfPred(region)) {
92 for (
Block &block : region) {
95 if (
auto term = dyn_cast<RegionBranchTerminatorOpInterface>(
96 block.getTerminator())) {
98 term.getSuccessorOperands(branchPoint)[*operandIndex], maxDepth,
100 }
else if (block.getNumSuccessors()) {
103 output.push_back(inputValue);
118 if (ViewLikeOpInterface view = dyn_cast<ViewLikeOpInterface>(op))
122 if (
auto branch = dyn_cast<RegionBranchOpInterface>(op)) {
128 output.push_back(result);
142 auto branch = dyn_cast<BranchOpInterface>((*it)->getTerminator());
145 output.push_back(arg);
150 unsigned index = it.getSuccessorIndex();
151 Value operand = branch.getSuccessorOperands(index)[argNumber];
154 output.push_back(arg);
165 if (
auto branch = dyn_cast<RegionBranchOpInterface>(op)) {
167 maxDepth, visited, output);
171 output.push_back(arg);
179 if (!visited.insert(value).second)
182 output.push_back(value);
213 std::optional<MemoryEffects::EffectInstance> &effect,
220 op = cast<OpResult>(value).getOwner();
221 MemoryEffectOpInterface
interface = dyn_cast<MemoryEffectOpInterface>(op);
232 if (llvm::isa<SideEffects::AutomaticAllocationScopeResource>(
233 effect->getResource())) {
250 Operation *lhsAllocScope =
nullptr, *rhsAllocScope =
nullptr;
251 std::optional<MemoryEffects::EffectInstance> lhsAlloc, rhsAlloc;
281 if (lhsHasAlloc == rhsHasAlloc) {
293 lhsAllocScope = rhsAllocScope;
305 if (rhsParentOp == lhsAllocScope) {
329 if (lhsValues.empty() || rhsValues.empty())
333 std::optional<AliasResult> result;
334 for (
Value lhsVal : lhsValues) {
335 for (
Value rhsVal : rhsValues) {
337 result = result ? result->merge(nextResult) : nextResult;
361 MemoryEffectOpInterface
interface = dyn_cast<MemoryEffectOpInterface>(op);
368 interface.getEffects(effects);
372 if (isa<MemoryEffects::Allocate, MemoryEffects::Free>(effect.getEffect()))
378 if (
Value effectValue = effect.getValue())
379 aliasResult =
alias(effectValue, location);
382 if (aliasResult.
isNo())
386 if (isa<MemoryEffects::Read>(effect.getEffect())) {
389 assert(isa<MemoryEffects::Write>(effect.getEffect()));
static LogicalResult getAllocEffectFor(Value value, std::optional< MemoryEffects::EffectInstance > &effect, Operation *&allocScopeOp)
Given a value, try to get an allocation effect attached to it.
static void collectUnderlyingAddressValues(Value value, unsigned maxDepth, DenseSet< Value > &visited, SmallVectorImpl< Value > &output)
Given a value, collect all of the underlying values being addressed.
static constexpr unsigned maxUnderlyingValueSearchDepth
The maximum depth that will be searched when trying to find an underlying value.
The possible results of an alias query.
bool isNo() const
Returns if this result indicates no possibility of aliasing.
@ MustAlias
The two locations precisely alias each other.
@ MayAlias
The two locations may or may not alias.
@ NoAlias
The two locations do not alias at all.
Attributes are known-constant values of operations.
This class represents an argument of a Block.
Block * getOwner() const
Returns the block that owns this argument.
unsigned getArgNumber() const
Returns the number of this argument.
Block represents an ordered list of Operations.
Region * getParent() const
Provide a 'getParent' method for ilist_node_with_parent methods.
pred_iterator pred_begin()
bool isEntryBlock()
Return if this block is the entry block in the parent region.
ModRefResult getModRef(Operation *op, Value location)
Return the modify-reference behavior of op on location.
virtual AliasResult aliasImpl(Value lhs, Value rhs)
Given the two values, return their aliasing behavior.
AliasResult alias(Value lhs, Value rhs)
Given two values, return their aliasing behavior.
The possible results of whether a memory access modifies or references a memory location.
bool isModAndRef() const
Returns if this result modifies and references memory.
ModRefResult merge(const ModRefResult &other)
Merge this ModRef result with other and return the result.
static ModRefResult getRef()
Return a new result that indicates that the memory access may reference the value stored in memory.
static ModRefResult getNoModRef()
Return a new result that indicates that the memory access neither references nor modifies the value s...
static ModRefResult getModAndRef()
Return a new result that indicates that the memory access may reference and may modify the value stor...
static ModRefResult getMod()
Return a new result that indicates that the memory access may modify the value stored in memory.
This is a value defined by a result of an operation.
Operation * getOwner() const
Returns the operation that owns this result.
unsigned getResultNumber() const
Returns the number of this result.
A trait of region holding operations that define a new scope for automatic allocations,...
This trait indicates that the memory effects of an operation includes the effects of operations neste...
Operation is the basic unit of execution within MLIR.
bool hasTrait()
Returns true if the operation was registered with a particular trait, e.g.
Operation * getParentOp()
Returns the closest surrounding operation that contains this operation or nullptr if this is a top-le...
OpTy getParentOfType()
Return the closest surrounding parent operation that is of type 'OpTy'.
Operation * getParentWithTrait()
Returns the closest surrounding parent operation with trait Trait.
MutableArrayRef< Region > getRegions()
Returns the regions held by this operation.
bool isProperAncestor(Operation *other)
Return true if this operation is a proper ancestor of the other operation.
This class represents a point being branched from in the methods of the RegionBranchOpInterface.
static constexpr RegionBranchPoint parent()
Returns an instance of RegionBranchPoint representing the parent operation.
This class represents a successor of a region.
This class contains a list of basic blocks and a link to the parent operation it is attached to.
Operation * getParentOp()
Return the parent operation this region is attached to.
This class represents a specific instance of an effect.
This class provides an abstraction over the different types of ranges over Values.
This class represents an instance of an SSA value in the MLIR system, representing a computable value...
Block * getParentBlock()
Return the Block in which this Value is defined.
Region * getParentRegion()
Return the Region in which this Value is defined.
This header declares functions that assist transformations in the MemRef dialect.
bool matchPattern(Value value, const Pattern &pattern)
Entry point for matching a pattern over a Value.
LogicalResult failure(bool isFailure=true)
Utility function to generate a LogicalResult.
bool succeeded(LogicalResult result)
Utility function that returns true if the provided LogicalResult corresponds to a success value.
LogicalResult success(bool isSuccess=true)
Utility function to generate a LogicalResult.
detail::constant_op_matcher m_Constant()
Matches a constant foldable operation.
This class represents an efficient way to signal success or failure.
The following effect indicates that the operation allocates from some resource.