LLVM 20.0.0git
MVETailPredication.cpp
Go to the documentation of this file.
1//===- MVETailPredication.cpp - MVE Tail Predication ------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9/// \file
10/// Armv8.1m introduced MVE, M-Profile Vector Extension, and low-overhead
11/// branches to help accelerate DSP applications. These two extensions,
12/// combined with a new form of predication called tail-predication, can be used
13/// to provide implicit vector predication within a low-overhead loop.
14/// This is implicit because the predicate of active/inactive lanes is
15/// calculated by hardware, and thus does not need to be explicitly passed
16/// to vector instructions. The instructions responsible for this are the
17/// DLSTP and WLSTP instructions, which setup a tail-predicated loop and the
18/// the total number of data elements processed by the loop. The loop-end
19/// LETP instruction is responsible for decrementing and setting the remaining
20/// elements to be processed and generating the mask of active lanes.
21///
22/// The HardwareLoops pass inserts intrinsics identifying loops that the
23/// backend will attempt to convert into a low-overhead loop. The vectorizer is
24/// responsible for generating a vectorized loop in which the lanes are
25/// predicated upon an get.active.lane.mask intrinsic. This pass looks at these
26/// get.active.lane.mask intrinsic and attempts to convert them to VCTP
27/// instructions. This will be picked up by the ARM Low-overhead loop pass later
28/// in the backend, which performs the final transformation to a DLSTP or WLSTP
29/// tail-predicated loop.
30//
31//===----------------------------------------------------------------------===//
32
33#include "ARM.h"
34#include "ARMSubtarget.h"
44#include "llvm/IR/IRBuilder.h"
46#include "llvm/IR/IntrinsicsARM.h"
49#include "llvm/Support/Debug.h"
54
55using namespace llvm;
56
57#define DEBUG_TYPE "mve-tail-predication"
58#define DESC "Transform predicated vector loops to use MVE tail predication"
59
61 "tail-predication", cl::desc("MVE tail-predication pass options"),
64 "Don't tail-predicate loops"),
66 "enabled-no-reductions",
67 "Enable tail-predication, but not for reduction loops"),
69 "enabled",
70 "Enable tail-predication, including reduction loops"),
72 "force-enabled-no-reductions",
73 "Enable tail-predication, but not for reduction loops, "
74 "and force this which might be unsafe"),
76 "force-enabled",
77 "Enable tail-predication, including reduction loops, "
78 "and force this which might be unsafe")));
79
80
81namespace {
82
83class MVETailPredication : public LoopPass {
85 Loop *L = nullptr;
86 ScalarEvolution *SE = nullptr;
87 TargetTransformInfo *TTI = nullptr;
88 const ARMSubtarget *ST = nullptr;
89
90public:
91 static char ID;
92
93 MVETailPredication() : LoopPass(ID) { }
94
95 void getAnalysisUsage(AnalysisUsage &AU) const override {
101 AU.setPreservesCFG();
102 }
103
104 bool runOnLoop(Loop *L, LPPassManager&) override;
105
106private:
107 /// Perform the relevant checks on the loop and convert active lane masks if
108 /// possible.
109 bool TryConvertActiveLaneMask(Value *TripCount);
110
111 /// Perform several checks on the arguments of @llvm.get.active.lane.mask
112 /// intrinsic. E.g., check that the loop induction variable and the element
113 /// count are of the form we expect, and also perform overflow checks for
114 /// the new expressions that are created.
115 const SCEV *IsSafeActiveMask(IntrinsicInst *ActiveLaneMask, Value *TripCount);
116
117 /// Insert the intrinsic to represent the effect of tail predication.
118 void InsertVCTPIntrinsic(IntrinsicInst *ActiveLaneMask, Value *Start);
119};
120
121} // end namespace
122
123bool MVETailPredication::runOnLoop(Loop *L, LPPassManager&) {
124 if (skipLoop(L) || !EnableTailPredication)
125 return false;
126
127 MaskedInsts.clear();
128 Function &F = *L->getHeader()->getParent();
129 auto &TPC = getAnalysis<TargetPassConfig>();
130 auto &TM = TPC.getTM<TargetMachine>();
131 ST = &TM.getSubtarget<ARMSubtarget>(F);
132 TTI = &getAnalysis<TargetTransformInfoWrapperPass>().getTTI(F);
133 SE = &getAnalysis<ScalarEvolutionWrapperPass>().getSE();
134 this->L = L;
135
136 // The MVE and LOB extensions are combined to enable tail-predication, but
137 // there's nothing preventing us from generating VCTP instructions for v8.1m.
138 if (!ST->hasMVEIntegerOps() || !ST->hasV8_1MMainlineOps()) {
139 LLVM_DEBUG(dbgs() << "ARM TP: Not a v8.1m.main+mve target.\n");
140 return false;
141 }
142
143 BasicBlock *Preheader = L->getLoopPreheader();
144 if (!Preheader)
145 return false;
146
147 auto FindLoopIterations = [](BasicBlock *BB) -> IntrinsicInst* {
148 for (auto &I : *BB) {
149 auto *Call = dyn_cast<IntrinsicInst>(&I);
150 if (!Call)
151 continue;
152
153 Intrinsic::ID ID = Call->getIntrinsicID();
154 if (ID == Intrinsic::start_loop_iterations ||
155 ID == Intrinsic::test_start_loop_iterations)
156 return cast<IntrinsicInst>(&I);
157 }
158 return nullptr;
159 };
160
161 // Look for the hardware loop intrinsic that sets the iteration count.
162 IntrinsicInst *Setup = FindLoopIterations(Preheader);
163
164 // The test.set iteration could live in the pre-preheader.
165 if (!Setup) {
166 if (!Preheader->getSinglePredecessor())
167 return false;
168 Setup = FindLoopIterations(Preheader->getSinglePredecessor());
169 if (!Setup)
170 return false;
171 }
172
173 LLVM_DEBUG(dbgs() << "ARM TP: Running on Loop: " << *L << *Setup << "\n");
174
175 bool Changed = TryConvertActiveLaneMask(Setup->getArgOperand(0));
176
177 return Changed;
178}
179
180// The active lane intrinsic has this form:
181//
182// @llvm.get.active.lane.mask(IV, TC)
183//
184// Here we perform checks that this intrinsic behaves as expected,
185// which means:
186//
187// 1) Check that the TripCount (TC) belongs to this loop (originally).
188// 2) The element count (TC) needs to be sufficiently large that the decrement
189// of element counter doesn't overflow, which means that we need to prove:
190// ceil(ElementCount / VectorWidth) >= TripCount
191// by rounding up ElementCount up:
192// ((ElementCount + (VectorWidth - 1)) / VectorWidth
193// and evaluate if expression isKnownNonNegative:
194// (((ElementCount + (VectorWidth - 1)) / VectorWidth) - TripCount
195// 3) The IV must be an induction phi with an increment equal to the
196// vector width.
197const SCEV *MVETailPredication::IsSafeActiveMask(IntrinsicInst *ActiveLaneMask,
198 Value *TripCount) {
199 bool ForceTailPredication =
202
203 Value *ElemCount = ActiveLaneMask->getOperand(1);
204 bool Changed = false;
205 if (!L->makeLoopInvariant(ElemCount, Changed))
206 return nullptr;
207
208 const SCEV *EC = SE->getSCEV(ElemCount);
209 const SCEV *TC = SE->getSCEV(TripCount);
210 int VectorWidth =
211 cast<FixedVectorType>(ActiveLaneMask->getType())->getNumElements();
212 if (VectorWidth != 2 && VectorWidth != 4 && VectorWidth != 8 &&
213 VectorWidth != 16)
214 return nullptr;
215 ConstantInt *ConstElemCount = nullptr;
216
217 // 1) Smoke tests that the original scalar loop TripCount (TC) belongs to
218 // this loop. The scalar tripcount corresponds the number of elements
219 // processed by the loop, so we will refer to that from this point on.
220 if (!SE->isLoopInvariant(EC, L)) {
221 LLVM_DEBUG(dbgs() << "ARM TP: element count must be loop invariant.\n");
222 return nullptr;
223 }
224
225 // 2) Find out if IV is an induction phi. Note that we can't use Loop
226 // helpers here to get the induction variable, because the hardware loop is
227 // no longer in loopsimplify form, and also the hwloop intrinsic uses a
228 // different counter. Using SCEV, we check that the induction is of the
229 // form i = i + 4, where the increment must be equal to the VectorWidth.
230 auto *IV = ActiveLaneMask->getOperand(0);
231 const SCEV *IVExpr = SE->getSCEV(IV);
232 auto *AddExpr = dyn_cast<SCEVAddRecExpr>(IVExpr);
233
234 if (!AddExpr) {
235 LLVM_DEBUG(dbgs() << "ARM TP: induction not an add expr: "; IVExpr->dump());
236 return nullptr;
237 }
238 // Check that this AddRec is associated with this loop.
239 if (AddExpr->getLoop() != L) {
240 LLVM_DEBUG(dbgs() << "ARM TP: phi not part of this loop\n");
241 return nullptr;
242 }
243 auto *Step = dyn_cast<SCEVConstant>(AddExpr->getOperand(1));
244 if (!Step) {
245 LLVM_DEBUG(dbgs() << "ARM TP: induction step is not a constant: ";
246 AddExpr->getOperand(1)->dump());
247 return nullptr;
248 }
249 auto StepValue = Step->getValue()->getSExtValue();
250 if (VectorWidth != StepValue) {
251 LLVM_DEBUG(dbgs() << "ARM TP: Step value " << StepValue
252 << " doesn't match vector width " << VectorWidth << "\n");
253 return nullptr;
254 }
255
256 if ((ConstElemCount = dyn_cast<ConstantInt>(ElemCount))) {
257 ConstantInt *TC = dyn_cast<ConstantInt>(TripCount);
258 if (!TC) {
259 LLVM_DEBUG(dbgs() << "ARM TP: Constant tripcount expected in "
260 "set.loop.iterations\n");
261 return nullptr;
262 }
263
264 // Calculate 2 tripcount values and check that they are consistent with
265 // each other. The TripCount for a predicated vector loop body is
266 // ceil(ElementCount/Width), or floor((ElementCount+Width-1)/Width) as we
267 // work it out here.
268 uint64_t TC1 = TC->getZExtValue();
269 uint64_t TC2 =
270 (ConstElemCount->getZExtValue() + VectorWidth - 1) / VectorWidth;
271
272 // If the tripcount values are inconsistent, we can't insert the VCTP and
273 // trigger tail-predication; keep the intrinsic as a get.active.lane.mask
274 // and legalize this.
275 if (TC1 != TC2) {
276 LLVM_DEBUG(dbgs() << "ARM TP: inconsistent constant tripcount values: "
277 << TC1 << " from set.loop.iterations, and "
278 << TC2 << " from get.active.lane.mask\n");
279 return nullptr;
280 }
281 } else if (!ForceTailPredication) {
282 // 3) We need to prove that the sub expression that we create in the
283 // tail-predicated loop body, which calculates the remaining elements to be
284 // processed, is non-negative, i.e. it doesn't overflow:
285 //
286 // ((ElementCount + VectorWidth - 1) / VectorWidth) - TripCount >= 0
287 //
288 // This is true if:
289 //
290 // TripCount == (ElementCount + VectorWidth - 1) / VectorWidth
291 //
292 // which what we will be using here.
293 //
294 const SCEV *VW =
295 SE->getSCEV(ConstantInt::get(TripCount->getType(), VectorWidth));
296 // ElementCount + (VW-1):
297 const SCEV *Start = AddExpr->getStart();
298 const SCEV *ECPlusVWMinus1 = SE->getAddExpr(
299 EC,
300 SE->getSCEV(ConstantInt::get(TripCount->getType(), VectorWidth - 1)));
301
302 // Ceil = ElementCount + (VW-1) / VW
303 const SCEV *Ceil = SE->getUDivExpr(ECPlusVWMinus1, VW);
304
305 // Prevent unused variable warnings with TC
306 (void)TC;
307 LLVM_DEBUG({
308 dbgs() << "ARM TP: Analysing overflow behaviour for:\n";
309 dbgs() << "ARM TP: - TripCount = " << *TC << "\n";
310 dbgs() << "ARM TP: - ElemCount = " << *EC << "\n";
311 dbgs() << "ARM TP: - Start = " << *Start << "\n";
312 dbgs() << "ARM TP: - BETC = " << *SE->getBackedgeTakenCount(L) << "\n";
313 dbgs() << "ARM TP: - VecWidth = " << VectorWidth << "\n";
314 dbgs() << "ARM TP: - (ElemCount+VW-1) / VW = " << *Ceil << "\n";
315 });
316
317 // As an example, almost all the tripcount expressions (produced by the
318 // vectoriser) look like this:
319 //
320 // TC = ((-4 + (4 * ((3 + %N) /u 4))<nuw> - start) /u 4)
321 //
322 // and "ElementCount + (VW-1) / VW":
323 //
324 // Ceil = ((3 + %N) /u 4)
325 //
326 // Check for equality of TC and Ceil by calculating SCEV expression
327 // TC - Ceil and test it for zero.
328 //
329 const SCEV *Div = SE->getUDivExpr(
330 SE->getAddExpr(SE->getMulExpr(Ceil, VW), SE->getNegativeSCEV(VW),
331 SE->getNegativeSCEV(Start)),
332 VW);
333 const SCEV *Sub = SE->getMinusSCEV(SE->getBackedgeTakenCount(L), Div);
334 LLVM_DEBUG(dbgs() << "ARM TP: - Sub = "; Sub->dump());
335
336 // Use context sensitive facts about the path to the loop to refine. This
337 // comes up as the backedge taken count can incorporate context sensitive
338 // reasoning, and our RHS just above doesn't.
339 Sub = SE->applyLoopGuards(Sub, L);
340 LLVM_DEBUG(dbgs() << "ARM TP: - (Guarded) = "; Sub->dump());
341
342 if (!Sub->isZero()) {
343 LLVM_DEBUG(dbgs() << "ARM TP: possible overflow in sub expression.\n");
344 return nullptr;
345 }
346 }
347
348 // Check that the start value is a multiple of the VectorWidth.
349 // TODO: This could do with a method to check if the scev is a multiple of
350 // VectorWidth. For the moment we just check for constants, muls and unknowns
351 // (which use MaskedValueIsZero and seems to be the most common).
352 if (auto *BaseC = dyn_cast<SCEVConstant>(AddExpr->getStart())) {
353 if (BaseC->getAPInt().urem(VectorWidth) == 0)
354 return SE->getMinusSCEV(EC, BaseC);
355 } else if (auto *BaseV = dyn_cast<SCEVUnknown>(AddExpr->getStart())) {
356 Type *Ty = BaseV->getType();
358 Log2_64(VectorWidth));
359 if (MaskedValueIsZero(BaseV->getValue(), Mask,
360 L->getHeader()->getDataLayout()))
361 return SE->getMinusSCEV(EC, BaseV);
362 } else if (auto *BaseMul = dyn_cast<SCEVMulExpr>(AddExpr->getStart())) {
363 if (auto *BaseC = dyn_cast<SCEVConstant>(BaseMul->getOperand(0)))
364 if (BaseC->getAPInt().urem(VectorWidth) == 0)
365 return SE->getMinusSCEV(EC, BaseC);
366 if (auto *BaseC = dyn_cast<SCEVConstant>(BaseMul->getOperand(1)))
367 if (BaseC->getAPInt().urem(VectorWidth) == 0)
368 return SE->getMinusSCEV(EC, BaseC);
369 }
370
372 dbgs() << "ARM TP: induction base is not know to be a multiple of VF: "
373 << *AddExpr->getOperand(0) << "\n");
374 return nullptr;
375}
376
377void MVETailPredication::InsertVCTPIntrinsic(IntrinsicInst *ActiveLaneMask,
378 Value *Start) {
379 IRBuilder<> Builder(L->getLoopPreheader()->getTerminator());
380 Module *M = L->getHeader()->getModule();
381 Type *Ty = IntegerType::get(M->getContext(), 32);
382 unsigned VectorWidth =
383 cast<FixedVectorType>(ActiveLaneMask->getType())->getNumElements();
384
385 // Insert a phi to count the number of elements processed by the loop.
386 Builder.SetInsertPoint(L->getHeader(), L->getHeader()->getFirstNonPHIIt());
387 PHINode *Processed = Builder.CreatePHI(Ty, 2);
388 Processed->addIncoming(Start, L->getLoopPreheader());
389
390 // Replace @llvm.get.active.mask() with the ARM specific VCTP intrinic, and
391 // thus represent the effect of tail predication.
392 Builder.SetInsertPoint(ActiveLaneMask);
393 ConstantInt *Factor = ConstantInt::get(cast<IntegerType>(Ty), VectorWidth);
394
395 Intrinsic::ID VCTPID;
396 switch (VectorWidth) {
397 default:
398 llvm_unreachable("unexpected number of lanes");
399 case 2: VCTPID = Intrinsic::arm_mve_vctp64; break;
400 case 4: VCTPID = Intrinsic::arm_mve_vctp32; break;
401 case 8: VCTPID = Intrinsic::arm_mve_vctp16; break;
402 case 16: VCTPID = Intrinsic::arm_mve_vctp8; break;
403 }
404 Function *VCTP = Intrinsic::getDeclaration(M, VCTPID);
405 Value *VCTPCall = Builder.CreateCall(VCTP, Processed);
406 ActiveLaneMask->replaceAllUsesWith(VCTPCall);
407
408 // Add the incoming value to the new phi.
409 // TODO: This add likely already exists in the loop.
410 Value *Remaining = Builder.CreateSub(Processed, Factor);
411 Processed->addIncoming(Remaining, L->getLoopLatch());
412 LLVM_DEBUG(dbgs() << "ARM TP: Insert processed elements phi: "
413 << *Processed << "\n"
414 << "ARM TP: Inserted VCTP: " << *VCTPCall << "\n");
415}
416
417bool MVETailPredication::TryConvertActiveLaneMask(Value *TripCount) {
418 SmallVector<IntrinsicInst *, 4> ActiveLaneMasks;
419 for (auto *BB : L->getBlocks())
420 for (auto &I : *BB)
421 if (auto *Int = dyn_cast<IntrinsicInst>(&I))
422 if (Int->getIntrinsicID() == Intrinsic::get_active_lane_mask)
423 ActiveLaneMasks.push_back(Int);
424
425 if (ActiveLaneMasks.empty())
426 return false;
427
428 LLVM_DEBUG(dbgs() << "ARM TP: Found predicated vector loop.\n");
429
430 for (auto *ActiveLaneMask : ActiveLaneMasks) {
431 LLVM_DEBUG(dbgs() << "ARM TP: Found active lane mask: "
432 << *ActiveLaneMask << "\n");
433
434 const SCEV *StartSCEV = IsSafeActiveMask(ActiveLaneMask, TripCount);
435 if (!StartSCEV) {
436 LLVM_DEBUG(dbgs() << "ARM TP: Not safe to insert VCTP.\n");
437 return false;
438 }
439 LLVM_DEBUG(dbgs() << "ARM TP: Safe to insert VCTP. Start is " << *StartSCEV
440 << "\n");
441 SCEVExpander Expander(*SE, L->getHeader()->getDataLayout(),
442 "start");
443 Instruction *Ins = L->getLoopPreheader()->getTerminator();
444 Value *Start = Expander.expandCodeFor(StartSCEV, StartSCEV->getType(), Ins);
445 LLVM_DEBUG(dbgs() << "ARM TP: Created start value " << *Start << "\n");
446 InsertVCTPIntrinsic(ActiveLaneMask, Start);
447 }
448
449 // Remove dead instructions and now dead phis.
450 for (auto *II : ActiveLaneMasks)
452 for (auto *I : L->blocks())
454 return true;
455}
456
458 return new MVETailPredication();
459}
460
461char MVETailPredication::ID = 0;
462
463INITIALIZE_PASS_BEGIN(MVETailPredication, DEBUG_TYPE, DESC, false, false)
464INITIALIZE_PASS_END(MVETailPredication, DEBUG_TYPE, DESC, false, false)
This file a TargetTransformInfo::Concept conforming object specific to the ARM target machine.
#define clEnumValN(ENUMVAL, FLAGNAME, DESC)
Definition: CommandLine.h:686
#define LLVM_DEBUG(X)
Definition: Debug.h:101
#define F(x, y, z)
Definition: MD5.cpp:55
#define I(x, y, z)
Definition: MD5.cpp:58
#define DESC
cl::opt< TailPredication::Mode > EnableTailPredication("tail-predication", cl::desc("MVE tail-predication pass options"), cl::init(TailPredication::Enabled), cl::values(clEnumValN(TailPredication::Disabled, "disabled", "Don't tail-predicate loops"), clEnumValN(TailPredication::EnabledNoReductions, "enabled-no-reductions", "Enable tail-predication, but not for reduction loops"), clEnumValN(TailPredication::Enabled, "enabled", "Enable tail-predication, including reduction loops"), clEnumValN(TailPredication::ForceEnabledNoReductions, "force-enabled-no-reductions", "Enable tail-predication, but not for reduction loops, " "and force this which might be unsafe"), clEnumValN(TailPredication::ForceEnabled, "force-enabled", "Enable tail-predication, including reduction loops, " "and force this which might be unsafe")))
#define DEBUG_TYPE
uint64_t IntrinsicInst * II
#define INITIALIZE_PASS_END(passName, arg, name, cfg, analysis)
Definition: PassSupport.h:57
#define INITIALIZE_PASS_BEGIN(passName, arg, name, cfg, analysis)
Definition: PassSupport.h:52
Target-Independent Code Generator Pass Configuration Options pass.
This pass exposes codegen information to IR-level passes.
static const uint32_t IV[8]
Definition: blake3_impl.h:78
Class for arbitrary precision integers.
Definition: APInt.h:78
static APInt getLowBitsSet(unsigned numBits, unsigned loBitsSet)
Constructs an APInt value that has the bottom loBitsSet bits set.
Definition: APInt.h:284
Represent the analysis usage information of a pass.
AnalysisUsage & addRequired()
AnalysisUsage & addPreserved()
Add the specified Pass class to the set of analyses preserved by this pass.
void setPreservesCFG()
This function should be called by the pass, iff they do not:
Definition: Pass.cpp:256
LLVM Basic Block Representation.
Definition: BasicBlock.h:61
const BasicBlock * getSinglePredecessor() const
Return the predecessor of this block if it has a single predecessor block.
Definition: BasicBlock.cpp:459
This is the shared class of boolean and integer constants.
Definition: Constants.h:81
uint64_t getZExtValue() const
Return the constant as a 64-bit unsigned integer value after it has been zero extended as appropriate...
Definition: Constants.h:155
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
Definition: IRBuilder.h:2686
static IntegerType * get(LLVMContext &C, unsigned NumBits)
This static method is the primary way of constructing an IntegerType.
Definition: Type.cpp:266
A wrapper class for inspecting calls to intrinsic functions.
Definition: IntrinsicInst.h:48
The legacy pass manager's analysis pass to compute loop information.
Definition: LoopInfo.h:593
virtual bool runOnLoop(Loop *L, LPPassManager &LPM)=0
Represents a single loop in the control flow graph.
Definition: LoopInfo.h:39
A Module instance is used to store all the information related to an LLVM module.
Definition: Module.h:65
void addIncoming(Value *V, BasicBlock *BB)
Add an incoming value to the end of the PHI list.
Pass interface - Implemented by all 'passes'.
Definition: Pass.h:94
virtual void getAnalysisUsage(AnalysisUsage &) const
getAnalysisUsage - This function should be overriden by passes that need analysis information to do t...
Definition: Pass.cpp:98
This class uses information about analyze scalars to rewrite expressions in canonical form.
This class represents an analyzed expression in the program.
bool isZero() const
Return true if the expression is a constant zero.
void dump() const
This method is used for debugging.
Type * getType() const
Return the LLVM type of this SCEV expression.
The main scalar evolution driver.
bool empty() const
Definition: SmallVector.h:94
void push_back(const T &Elt)
Definition: SmallVector.h:426
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1209
Primary interface to the complete machine description for the target machine.
Definition: TargetMachine.h:77
Target-Independent Code Generator Pass Configuration Options.
Wrapper pass for TargetTransformInfo.
This pass provides access to the codegen interfaces that are needed for IR-level transformations.
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
TypeSize getPrimitiveSizeInBits() const LLVM_READONLY
Return the basic size of this type if it is a primitive type.
Value * getOperand(unsigned i) const
Definition: User.h:169
LLVM Value Representation.
Definition: Value.h:74
Type * getType() const
All values are typed, get the type of this value.
Definition: Value.h:255
void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
Definition: Value.cpp:534
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
Definition: BitmaskEnum.h:121
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition: CallingConv.h:24
Function * getDeclaration(Module *M, ID id, ArrayRef< Type * > Tys=std::nullopt)
Create or insert an LLVM Function declaration for an intrinsic, and return it.
Definition: Function.cpp:1539
ValuesClass values(OptsTy... Options)
Helper to build a ValuesClass by forwarding a variable number of arguments as an initializer list to ...
Definition: CommandLine.h:711
initializer< Ty > init(const Ty &Val)
Definition: CommandLine.h:443
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
void dump(const SparseBitVector< ElementSize > &LHS, raw_ostream &out)
bool RecursivelyDeleteTriviallyDeadInstructions(Value *V, const TargetLibraryInfo *TLI=nullptr, MemorySSAUpdater *MSSAU=nullptr, std::function< void(Value *)> AboutToDeleteCallback=std::function< void(Value *)>())
If the specified value is a trivially dead instruction, delete it.
Definition: Local.cpp:540
bool MaskedValueIsZero(const Value *V, const APInt &Mask, const SimplifyQuery &DL, unsigned Depth=0)
Return true if 'V & Mask' is known to be zero.
unsigned Log2_64(uint64_t Value)
Return the floor log base 2 of the specified value, -1 if the value is zero.
Definition: MathExtras.h:346
bool DeleteDeadPHIs(BasicBlock *BB, const TargetLibraryInfo *TLI=nullptr, MemorySSAUpdater *MSSAU=nullptr)
Examine each PHI in the given block and delete it if it is dead.
Pass * createMVETailPredicationPass()
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition: Debug.cpp:163