16#ifndef LLVM_LIB_TRANSFORMS_VECTORIZE_SLPVECTORIZER_SLPCOMPATIBILITYANALYSIS_H
17#define LLVM_LIB_TRANSFORMS_VECTORIZE_SLPVECTORIZER_SLPCOMPATIBILITYANALYSIS_H
48 using MaskType = std::uint_fast32_t;
50 constexpr static unsigned SupportedOp[] = {
51 Instruction::Add, Instruction::FAdd, Instruction::Sub, Instruction::FSub,
52 Instruction::Mul, Instruction::Shl, Instruction::AShr, Instruction::And,
53 Instruction::Or, Instruction::Xor};
55 "SupportedOp is not sorted.");
76 static std::pair<Constant *, unsigned>
78 struct InterchangeableInfo {
81 MaskType Mask = MainOpBIT | XorBIT | OrBIT | AndBIT | SubBIT | AddBIT |
82 MulBIT | AShrBIT | ShlBIT | FSubBIT | FAddBIT;
87 MaskType SeenBefore = 0;
92 bool trySet(MaskType OpcodeInMaskForm, MaskType InterchangeableMask);
93 bool equal(
unsigned Opcode) {
94 return Opcode ==
I->getOpcode() && trySet(MainOpBIT, MainOpBIT);
96 unsigned getOpcode()
const;
97 bool hasDefinedOpcode()
const {
return (Mask & SeenBefore) > 0; }
102 InterchangeableInfo MainOp;
103 InterchangeableInfo AltOp;
110 : MainOp(MainOp), AltOp(AltOp) {}
116 return MainOp.hasCandidateOpcode(Opcode);
123 return !
hasAltOp() || AltOp.hasDefinedOpcode();
126 return MainOp.getOperand(
I);
157 bool HasCopyables =
false;
160 unsigned CopyableOpIdx = 0;
163 bool AbsorbCopyableFMul =
false;
167 assert(
valid() &&
"InstructionsState is invalid.");
172 assert(
valid() &&
"InstructionsState is invalid.");
215 return (
getOpcode() == Instruction::ICmp ||
221 bool valid()
const {
return MainOp && AltOp; }
227 bool HasCopyables =
false)
228 : MainOp(MainOp), AltOp(AltOp), HasCopyables(HasCopyables),
250 assert(
valid() &&
"InstructionsState is invalid.");
256 assert(
valid() &&
"InstructionsState is invalid.");
257 return CopyableOpIdx;
262 assert((Idx == 0 || Idx == 2) &&
"Unexpected copyable operand index.");
268 assert(
valid() &&
"InstructionsState is invalid.");
269 return AbsorbCopyableFMul;
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
This file defines the SmallVector class.
Represent a constant reference to an array (0 or more elements consecutively in memory),...
This is an important base class in LLVM.
static bool isBitwiseLogicOp(unsigned Opcode)
Determine if the Opcode is and/or/xor.
unsigned getOpcode() const
Returns a member of one of the enums like Instruction::Add.
The RecurrenceDescriptor is used to identify recurrences variables in a loop.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
LLVM Value Representation.
SmallVector< Value * > getOperand(const Instruction *I) const
bool hasDefinedMainOpcode() const
unsigned getAltOpcode() const
bool hasDefinedAltOpcode() const
bool add(const Instruction *I)
bool hasCandidateOpcode(unsigned Opcode) const
Checks if the list of potential opcodes includes Opcode.
BinOpSameOpcodeHelper(const Instruction *MainOp, const Instruction *AltOp=nullptr)
unsigned getMainOpcode() const
Instruction * getMainOp() const
bool hasAbsorbedCopyableFMul() const
Checks if copyable fmuls are absorbed as fmuladd(a, b, -0.0).
Instruction * getMatchingMainOpOrAltOp(Instruction *I) const
Checks if the instruction matches either the main or alternate opcode.
bool areInstructionsWithCopyableElements() const
Checks if the state represents copyable instructions.
unsigned getAltOpcode() const
bool isCmpOp() const
Checks if main/alt instructions are cmp operations.
static InstructionsState invalid()
static bool isSameOperation(const Instruction *I, const Instruction *Op)
Checks if I is the same operation as Op, distinguishing calls by intrinsic ID (all calls share the Ca...
bool valid() const
Checks if the current state is valid, i.e. has non-null MainOp.
bool isExpandedBinOp(Value *V) const
Checks if the value V is a transformed instruction, compatible either with main or alternate ops.
bool isAddSubLikeOp() const
Checks if main/alt instructions are add/sub/fadd/fsub operations.
bool isShiftOp() const
Checks if main/alt instructions are shift operations.
bool isExpandedOperand(Instruction *I, unsigned Idx) const
Checks if the operand at index Idx of instruction I is an expanded operand.
bool isCopyableElement(Value *V) const
Checks if the value is a copyable element.
bool isAltShuffle() const
Some of the instructions in the list have alternate opcodes.
void setCopyableOpIdx(unsigned Idx)
Sets the index of the operand the copyable value is modeled in.
Instruction * getAltOp() const
InstructionsState()=delete
InstructionsState(Instruction *MainOp, Instruction *AltOp, bool HasCopyables=false)
bool isNonSchedulable(Value *V) const
Checks if the value is non-schedulable.
unsigned getCopyableOpIdx() const
Returns the index of the operand the copyable value is modeled in.
bool isBitwiseLogicOp() const
Checks if main/alt instructions are bitwise logic operations.
void setAbsorbCopyableFMul(bool Absorb)
Sets the absorbed-fmul modeling for copyable fmuls.
bool isMulDivLikeOp() const
Checks if main/alt instructions are mul/div/rem/fmul/fdiv/frem operations.
unsigned getOpcode() const
The main/alternate opcodes for the list of instructions.
A private "module" namespace for types and utilities used by this pass.
bool isValidForAlternation(unsigned Opcode)
bool isAbsorbableFMul(ArrayRef< Value * > VL, Value *V)
Checks if V is a single-use fmul with operands outside VL.
bool isAbsorbableCopyableFMul(const InstructionsState &S, Value *V)
Checks if V is a copyable single-use fmul, absorbable as fmuladd(a, b, -0.0).
This is an optimization pass for GlobalISel generic memory operations.
@ LLVM_MARK_AS_BITMASK_ENUM
constexpr bool is_sorted_constexpr(R &&Range, Cmp C=Cmp{})
Check if elements in a range R are sorted with respect to a comparator C.
DWARFExpression::Operation Op
bool equal(L &&LRange, R &&RRange)
Wrapper function around std::equal to detect if pair-wise elements between two ranges are the same.